package com.md.config.aliyun.oss;

import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.auth.sts.AssumeRoleRequest;
import com.aliyuncs.auth.sts.AssumeRoleResponse;
import com.aliyuncs.exceptions.ClientException;
import com.aliyuncs.http.MethodType;
import com.aliyuncs.profile.DefaultProfile;
import com.aliyuncs.profile.IClientProfile;
import com.md.base.exception.ServerException;
import com.md.model.bo.SecretKey;
import com.md.value.enums.ErrorEnum;
import lombok.extern.slf4j.Slf4j;

import java.io.InputStream;
import java.util.UUID;

/**
 * @author 刘骄阳
 * 2024-02-23 16:37
 */
@Slf4j
public class OSSClient {
  public OSS newInstance(final OSSConfig ossConfig, final String salt) {
    SecretKey secretKey = SecretKey.decoding(ossConfig.getAccessKey(), ossConfig.getAccessKeySecret(), salt);
    AssumeRoleResponse assumeRoleResponse = fetchSTSToken(ossConfig, secretKey);
    AssumeRoleResponse.Credentials credentials = assumeRoleResponse.getCredentials();
    return new OSSClientBuilder().build(ossConfig.getOssEndpoint(), credentials.getAccessKeyId(),
      credentials.getAccessKeySecret(), credentials.getSecurityToken());

  }

  public AssumeRoleResponse fetchSTSToken(final OSSConfig ossConfig, final SecretKey secretKey) {
    try {
      DefaultProfile.addEndpoint(ossConfig.getRegionId(), ossConfig.getProduct(), ossConfig.getStsEndpoint());
      IClientProfile profile = DefaultProfile.getProfile(ossConfig.getRegionId(),
        secretKey.getAccessKey(),
        secretKey.getAccessKeySecret());
      DefaultAcsClient client = new DefaultAcsClient(profile);
      AssumeRoleRequest request = new AssumeRoleRequest();
      request.setSysMethod(MethodType.POST);
      request.setRoleArn(ossConfig.getRoleArn());
      request.setRoleSessionName(UUID.randomUUID().toString());
      request.setDurationSeconds(ossConfig.getExpiration());
      return client.getAcsResponse(request);
    } catch (ClientException var6) {
      log.error("Error code: {}", var6.getErrCode());
      log.error("Error message: {}", var6.getErrMsg());
      log.error("RequestId: {}", var6.getRequestId());
      throw ServerException.build(ErrorEnum.SYSTEM_ERROR);
    }
  }

  public String uploadOSS(final InputStream inputStream, final String objectName,
                          final OSSConfig ossConfig, final String salt) {
    // 创建OSSClient实例。
    OSS ossClient = newInstance(ossConfig, salt);
    try {
      String fileName = ossConfig.getFilePrefix() + objectName;
      //上传文件
      ossClient.putObject(ossConfig.getBucketName(), fileName, inputStream);
      // 封装  url 路径
      return String.join("/", ossConfig.getHostname(), fileName);
    } catch (Exception ex) {
      log.error("error by {}", ex.getMessage());
      throw ServerException.of(ErrorEnum.UPLOAD_FILE_ERROR);
    } finally {
      ossClient.shutdown();
    }
  }
}
